package com.core.script;

import java.io.File;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.util.HashMap;

import org.apache.log4j.Logger;

import com.core.utils.ClassUtils;
import com.core.utils.FileUtils;
import com.core.utils.ScriptUtils;
/**
 * 脚本管理类
 * @author King
 *
 */
public abstract class ScriptManager {

	private Logger log = Logger.getLogger(ScriptManager.class);

	private HashMap<Integer, IScript> scripts = new HashMap<Integer, IScript>();
	
	private HashMap<Integer, Class<IScript>> scriptClass = new HashMap<Integer, Class<IScript>>();

	public void init(){
		File file = new File("bin");
		if(!file.exists()){
			file.mkdir();
		}
		loadScript();
	}
	
	
	/**注册脚本**/
	public void register(IScript script)
	{
		if(scripts.containsKey(script.getId()))
		{
			System.err.println("脚本id有重复:"+script.getId());
			Thread.dumpStack();
		}
		scripts.put(script.getId(), script);
	}
	/**
	 * 重加载
	 * @param path 脚本类(格式如Name,需要将Name.java放入指定的bin目录下面)
	 * @param playerId
	 */
	@SuppressWarnings("unchecked")
	public void reloadScript(String scriptName,HashMap<Integer, IScript> scripts)
	{
		File file = new File("bin");
		if(!file.exists()){
			file.mkdir();
		}
		try{
			if(scriptName==null || "".equals(scriptName)) return;
			String absPath = file.getAbsolutePath()+File.separatorChar+scriptName.replace("\\", "/");
			//截取包名
			String packageName = ClassUtils.getClassPackage(absPath.replace('.', '/') + ".java");
			
			//获得java文件内容
			String content = FileUtils.readStringFileUTF8(absPath.replace('.', '/') + ".java");
			
			boolean compilerSucceed = ScriptUtils.getInstance().compilerJavaCode(packageName+"."+scriptName, content);
			if(!compilerSucceed)
				return;
			
			Class<?> clazz = ScriptUtils.getInstance().loadClass(packageName+"."+scriptName);
			if(clazz!=null){
				IScript o = (IScript)clazz.newInstance();
				scriptClass.put(o.getId(), (Class<IScript>)clazz);
				scripts.put(o.getId(), o);
				log.error("脚本"+scriptName+"加载成功");
			}
		}catch(FileNotFoundException e){
			log.error(e, e);
		}catch(IllegalAccessException e){
			log.error(e, e);
		}catch(InstantiationException e){
			log.error(e, e);
		}catch(IOException e){
			log.error(e, e);
		}catch(Exception e){
			log.error(e, e);
		}
	}
	
	
//	public String reloadbybg(int id, String resulthttp){
//		File file = new File("bin");
//		if(!file.exists()){
//			file.mkdir();
//		}
//		Q_scriptBean script = ManagerPool.dataManager.q_scriptContainer.getMap().get(id);
//		if(script!=null){
//			try{
//				if(script.getQ_script_name()==null || "".equals(script.getQ_script_name())) return "-1";
//				InputStream in = new FileInputStream(script.getQ_script_name().replace('.', '/') + ".java");
//				StringBuffer buff = new StringBuffer();
//
//				IoBuffer buf = IoBuffer.allocate(10240);
//				buf.setAutoExpand(true);
//				buf.setAutoShrink(true);
//				
//				byte[] bytes = new byte[1024];
//				int len = 0;
//				while((len=in.read(bytes)) != -1){
//					buf.put(bytes, 0, len);
//				}
//				buf.flip();
//				
//				byte[] allbytes = new byte[buf.remaining()];
//				buf.get(allbytes);
//				buff.append(new String(allbytes, "UTF-8"));
//				in.close();
//				
//				Class<?> clazz = javaCodeToObject(script.getQ_script_name(), buff.toString());
//				if(clazz!=null){
//					IScript o = (IScript)clazz.newInstance();
//					scripts.put(o.getId(), o);
//					
//					log.error("脚本"+id+"加载成功");
//					HttpUtil.wget(resulthttp+"&result=1&location=world");
//					
//					return "1";
//				}
//			}catch(FileNotFoundException e){
//				log.error(e, e);
//			}catch(IllegalAccessException e){
//				log.error(e, e);
//			}catch(InstantiationException e){
//				log.error(e, e);
//			}catch(IOException e){
//				log.error(e, e);
//			}catch(Exception e){
//				log.error(e, e);
//			}
//			try {
//				HttpUtil.wget(resulthttp+"&result=0&location=world&tip="+id);
//			} catch (Exception e) {
//				log.error(e, e);
//			}
//		}
//		return "-2";
//	}
	
//	public void load(String scriptName, long roleId){
//		File file = new File("bin");
//		if(!file.exists()){
//			file.mkdir();
//		}
//		try{
//			if(scriptName==null || "".equals(scriptName)) return;
//			InputStream in = new FileInputStream(scriptName.replace('.', '/') + ".java");
//			StringBuffer buff = new StringBuffer();
//
//			IoBuffer buf = IoBuffer.allocate(10240);
//			buf.setAutoExpand(true);
//			buf.setAutoShrink(true);
//			
//			byte[] bytes = new byte[1024];
//			int len = 0;
//			while((len=in.read(bytes)) != -1){
//				buf.put(bytes, 0, len);
//			}
//			buf.flip();
//			
//			byte[] allbytes = new byte[buf.remaining()];
//			buf.get(allbytes);
//			buff.append(new String(allbytes, "UTF-8"));
//			in.close();
//			
//			Class<?> clazz = javaCodeToObject(scriptName, buff.toString());
//			if(clazz!=null){
//				IScript o = (IScript)clazz.newInstance();
//				scripts.put(o.getId(), o);
//				
//				IPlayer player = LogicEngin.getCache().getPlayerById(roleId);
//				if(player!=null){
//					Information.newInformation("重加载脚本{1}成功:"+scriptName).send(LogicEngin.getEngin(), player);
//				}
//				log.error("脚本"+scriptName+"加载成功");
//			}
//		}catch(FileNotFoundException e){
//			log.error(e, e);
//		}catch(IllegalAccessException e){
//			log.error(e, e);
//		}catch(InstantiationException e){
//			log.error(e, e);
//		}catch(IOException e){
//			log.error(e, e);
//		}catch(Exception e){
//			log.error(e, e);
//		}
//	}
	
//	public String loadByBg(String scriptName,String httpresult){
//		File file = new File("bin");
//		if(!file.exists()){
//			file.mkdir();
//		}
//		try{
//			if(scriptName==null || "".equals(scriptName)) return "-1";
//			InputStream in = new FileInputStream(scriptName.replace('.', '/') + ".java");
//			StringBuffer buff = new StringBuffer();
//
//			IoBuffer buf = IoBuffer.allocate(10240);
//			buf.setAutoExpand(true);
//			buf.setAutoShrink(true);
//			
//			byte[] bytes = new byte[1024];
//			int len = 0;
//			while((len=in.read(bytes)) != -1){
//				buf.put(bytes, 0, len);
//			}
//			buf.flip();
//			
//			byte[] allbytes = new byte[buf.remaining()];
//			buf.get(allbytes);
//			buff.append(new String(allbytes, "UTF-8"));
//			in.close();
//			
//			Class<?> clazz = javaCodeToObject(scriptName, buff.toString());
//			if(clazz!=null){
//				IScript o = (IScript)clazz.newInstance();
//				scripts.put(o.getId(), o);
//				
////			TODO	HttpUtil.wget(httpresult+"&result=1&location=world");
//				log.error("脚本"+scriptName+"加载成功");
//				return "1";
//			}
//		}catch(FileNotFoundException e){
//			log.error(e, e);
//		}catch(IllegalAccessException e){
//			log.error(e, e);
//		}catch(InstantiationException e){
//			log.error(e, e);
//		}catch(IOException e){
//			log.error(e, e);
//		}catch(Exception e){
//			log.error(e, e);
//		}
//		return "-2";
//	}
	
	@SuppressWarnings("unchecked")
	public <T extends IScript> T getScript(int ScriptEnum){
		return (T)scripts.get(ScriptEnum);
	}
	
	public void setScripts(HashMap<Integer, IScript> scripts) {
		this.scripts = scripts;
	}

	public HashMap<Integer, IScript> getScripts() {
		return scripts;
	}


//	public void excute(int scriptId, String method, Object... paras){
//		ScriptsUtils.call(scriptId, method, paras);
//	}
//	
//	public void excuteFromGame(int scriptId, String method, List<String> paras){
//		ScriptsUtils.callFromGame(scriptId, method, paras);
//	}
	
	/**加载脚本**/
	public abstract void loadScript();
}
